package com.arrcen.medicen.core.match.utlity;


import com.baomidou.mybatisplus.annotation.IdType;
import com.baomidou.mybatisplus.annotation.TableField;
import com.baomidou.mybatisplus.annotation.TableId;
import com.baomidou.mybatisplus.annotation.TableName;
import org.apache.commons.lang3.StringUtils;

import java.lang.reflect.Field;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

public class EntityHelper<T> {

    public String tableName;
    public String dbKey;
    public IdType dbKeyType;
    public String classKey;
    public T data;
    public Class<T> classType;

    public EntityHelper(Class<T> _classType){
        classType=_classType;
        try {
            data=classType.newInstance();
        } catch (InstantiationException e) {
            e.printStackTrace();
        } catch (IllegalAccessException e) {
            e.printStackTrace();
        }
        this.tableName=getTableName(this.data);
        getKey(this.data);
    }


    public EntityHelper(T _inClass){
        this.data=_inClass;
        classType=(Class<T>)_inClass.getClass();

        this.tableName=getTableName(_inClass);
        getKey(_inClass);
    }

    public T getMyClass(){
        return data;
    }

    /**
     * 获取对象名值，和值
     * @param saveFieldList
     * @param ignoreFieldList
     * @return
     */
    public Map getEntityMapValue(List<String> saveFieldList, List<String> ignoreFieldList){
        HashMap<String ,Object> info = new HashMap<String ,Object>();
        Field[] fields = data.getClass().getDeclaredFields();//获取类成员变量
        for (Field field: fields) {//遍历
            if (
                    (saveFieldList != null && saveFieldList.size() != 0 && !saveFieldList.contains(field.getName())) ||
                            (ignoreFieldList != null && ignoreFieldList.size() != 0 && ignoreFieldList.contains(field.getName()))
                    ) {
                continue;
            }
            if (field.isAnnotationPresent(TableField.class)) {//判断是不是EmployeeName类型注解
                TableField column = field.getAnnotation(TableField.class);
                if(!column.exist()) continue;;
                Object value = null;
                try {
                    value = field.get(data);
                } catch (IllegalAccessException e) {
                    e.printStackTrace();
                }
                if (value != null && column != null && column.value() != null) {
                    info.put(column.value(), value);//获取注解的值
                }
            }
            else if(field.isAnnotationPresent(TableId.class)) {
                TableId column = field.getAnnotation(TableId.class);
                Object value = null;
                try {
                    value = field.get(data);
                } catch (IllegalAccessException e) {
                    e.printStackTrace();
                }
                if (value != null && column != null && column.value() != null) {
                    info.put(column.value(), value);//获取注解的值
                }
            }
            else {
                Object value = null;
                try {
                    value = field.get(data);
                } catch (IllegalAccessException e) {
                    e.printStackTrace();
                }
                if (value != null ) {
                    info.put(field.getName(), value);
                }
            }
        }
        return info;
    }

    /**
     * 字段和占位符
     * @param saveFieldList
     * @param ignoreFieldList
     * @return
     */
    public  HashMap<String, String> getEntityMapMybits(List<String> saveFieldList, List<String> ignoreFieldList) {
        HashMap<String, String> info = new HashMap<String, String>();
        Field[] fields = data.getClass().getDeclaredFields();//获取类成员变量
        for (Field field : fields) {//遍历
            if (
                    (saveFieldList != null && saveFieldList.size() != 0 && !saveFieldList.contains(field.getName())) ||
                            (ignoreFieldList != null && ignoreFieldList.size() != 0 && ignoreFieldList.contains(field.getName()))
                    ) {
                continue;
            }
            if (field.isAnnotationPresent(TableField.class)) {//判断是不是EmployeeName类型注解
                TableField column = field.getAnnotation(TableField.class);
                if(!column.exist())continue;
                info.put(column.value() == null || column.value().equals("") ? field.getName() : column.value(), "#{data.data." + field.getName() + "}");//获取注解的值
            }
            else if(field.isAnnotationPresent(TableId.class)) {
                TableId column = field.getAnnotation(TableId.class);
                info.put(column.value() == null || column.value().equals("") ? field.getName() : column.value(), "#{data.data." + field.getName() + "}");//获取注解的值
            }
            else {
                info.put(field.getName(), "#{data.data." + field.getName() + "}");//获取注解的值
            }
        }
        return info;
    }

    /**
     * 获取属于和字段，用于查询替换
     * @return
     */
    public  HashMap<String, String> getEntityMapNameColumn() {
        HashMap<String, String> info = new HashMap<String, String>();
        Field[] fields = data.getClass().getDeclaredFields();//获取类成员变量
        for (Field field : fields) {//遍历
            if (field.isAnnotationPresent(TableField.class)) {//判断是不是EmployeeName类型注解
                TableField column = field.getAnnotation(TableField.class);
                if (!column.exist()) continue;
                info.put(field.getName(), column.value() == null || column.value().equals("") ? field.getName() : column.value());//获取注解的值
            }
            else if(field.isAnnotationPresent(TableId.class)) {
                TableId column = field.getAnnotation(TableId.class);
                info.put(field.getName(), column.value() == null || column.value().equals("") ? field.getName() : column.value());//获取注解的值
            }
            else {
                info.put(field.getName(), field.getName());//获取注解的值
            }
        }
        return info;
    }



    /**
     * 获取表名
     * @param clazz
     * @param <T>
     * @return
     */
    protected <T> String getTableName(T clazz) {
        if (clazz.getClass().isAnnotationPresent(TableName.class)) {
            TableName type = clazz.getClass().getAnnotation(TableName.class);
            return type.value();
        } else {
            return clazz.getClass().getName();
        }
    }




    /**
     * 获取所有查询别名数据，用于查询
     * @param allItems
     * @return
     */
    public List<String> getSelectFiledList(List<String> allItems) {
        List<String> reList = new ArrayList<>();
        Field[] fields = this.data.getClass().getDeclaredFields();//获取类成员变量
        for (Field field : fields) {//遍历
            //判断是不是EmployeeName类型注解
            if (field.isAnnotationPresent(TableField.class) && (allItems == null || allItems.size() == 0 || allItems.contains(field.getName()))) {
                TableField column = field.getAnnotation(TableField.class);
                if(!column.exist())continue;
                if (StringUtils.isAnyEmpty(column.value())) {
                    reList.add(field.getName());
                } else {
                    reList.add(column.value() + " " + field.getName());
                }
            }
            else if(field.isAnnotationPresent(TableId.class)) {
                TableId column = field.getAnnotation(TableId.class);
                if (StringUtils.isAnyEmpty(column.value())) {
                    reList.add(field.getName());
                } else {
                    reList.add(column.value() + " " + field.getName());
                }
            }
            else  {
                reList.add(field.getName());
            }
        }
        return reList;
    }

    /**
     * 获取主键
     * @param clazz
     * @return
     * @throws Exception
     */
    protected void getKey(T clazz){
        Field[] fields = clazz.getClass().getDeclaredFields();//获取类成员变量
        for (Field field: fields) {//遍历
            //判断是不是EmployeeName类型注解
            if (field.isAnnotationPresent(TableId.class)) {
                TableId column = field.getAnnotation(TableId.class);
                this.dbKeyType = column.type();
                this.dbKey = StringUtils.isAnyBlank(column.value()) ? field.getName() : column.value();
                this.classKey = field.getName();
                return;
            }
        }
    }

}
